package com.alibaba.dubbo.rpc;

import com.alibaba.dubbo.common.extension.ExtensionLoader;

/**
 * 一个接口的实现者可能有多个，此时到底注入哪一个呢？
 * 此时采取的策略是，并不去注入一个具体的实现者，而是注入一个动态生成的实现者，这个动态生成的实现者的逻辑是确定的，能够根据不同的参数来使用不同的实现者实现相应的方法。这个动态生成的实现者的class就是ExtensionLoader的Class<?> cachedAdaptiveClass
 *
 * 生成的扩展类
 */
public class Protocol$Adpative implements
        com.alibaba.dubbo.rpc.Protocol {
    @Override
    public void destroy() {
        throw new UnsupportedOperationException("method public abstract void com.alibaba.dubbo.rpc.Protocol.destroy() of interface com.alibaba.dubbo.rpc.Protocol is not adaptive method !");
    }

    @Override
    public int getDefaultPort() {
        throw new UnsupportedOperationException("method public abstract int com.alibaba.dubbo.rpc.Protocol.getDefaultPort() of interface com.alibaba.dubbo.rpc.Protocol is not adaptive method !");
    }

    @Override
    public com.alibaba.dubbo.rpc.Exporter export(com.alibaba.dubbo.rpc.Invoker arg0) throws RpcException {
        if (arg0 == null) throw new
                IllegalArgumentException("com.alibaba.dubbo.rpc.Invoker argument == null ");
        if (arg0.getUrl() == null) throw new
                IllegalArgumentException("com.alibaba.dubbo.rpc.Invoker argument getUrl() == null");
        //获取URL参数
        com.alibaba.dubbo.common.URL url = arg0.getUrl();
        //获取协议类型，获取的协议实际是Adaptive注解的方法必须含有URL类型的参数
        String extName = (url.getProtocol() == null ? "dubbo" :
                url.getProtocol());
        //协议为空抛异常
        if (extName == null)
            throw new IllegalStateException("Fail to get extension(com.alibaba.dubbo.rpc.Protocol)name from url(" + url.toString() + ") use keys([protocol])");
        //根据协议类型动态加载对应的扩展点
        com.alibaba.dubbo.rpc.Protocol extension =
                (com.alibaba.dubbo.rpc.Protocol) ExtensionLoader.getExtensionLoader(com.alibaba.dubbo.rpc.Protocol.class).getExtension(extName);
        return extension.export(arg0);
    }

    @Override
    public com.alibaba.dubbo.rpc.Invoker refer(Class arg0,
                                               com.alibaba.dubbo.common.URL arg1) throws RpcException {
        if (arg1 == null) throw new IllegalArgumentException("url == null ");
        com.alibaba.dubbo.common.URL url = arg1;
        String extName = (url.getProtocol() == null ? "dubbo" : url.getProtocol());
        if (extName == null)
            throw new IllegalStateException("Fail to get extension(com.alibaba.dubbo.rpc.Protocol)name from url(" + url.toString() + ") use keys([protocol])");
        com.alibaba.dubbo.rpc.Protocol extension =
                (com.alibaba.dubbo.rpc.Protocol) ExtensionLoader.getExtensionLoader(com.alibaba.dubbo.rpc.Protocol.class).getExtension(extName);
        return extension.refer(arg0, arg1);
    }
}